package ddd.ajava.chapter2.question11;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;

import ddd.ajava.util.StringUtil;

public class ConvertBtnPersonAndMap {
	public static void main(String[] args) {
		ConvertBtnPersonAndMap convert=new ConvertBtnPersonAndMap();
		Person person=new Person();
		person.setIdNo("5122245566");
		person.setName("张小平");
		person.setAge(23);
		person.setSex("Male");
		person.setIsMerried(true);
		
		Map map=convert.convertPerson2Map(person);
		convert.mapIterator(map);
		System.out.println();
		Person p=convert.convertMap2Person(map);
		System.out.println(p.toString());
	}
	
	/**
	 * @param person
	 * @return
	 * 反射将Person中的属性名及值存入Map中
	 * 1.获取所有属性
	 * 2.通过get取得属性值
	 * 3.将属性看做键，属性值看做值，存入Map中
	 */
	public Map convertPerson2Map(Person person){
		Map<String,String> personMap=new HashMap<String,String>();
		
		Class clazz=person.getClass();
		Field[] fields=clazz.getDeclaredFields();
		for(Field f:fields){
			String fieldName=f.getName();
			String methodName="get"+StringUtil.firstCharToUpper(fieldName);
			try {
				Method method=clazz.getMethod(methodName);
				Object value=method.invoke(person);
				personMap.put(fieldName, value.toString());
			} catch (SecurityException e) {
				e.printStackTrace();
			} catch (NoSuchMethodException e) {
				e.printStackTrace();
			} catch (IllegalArgumentException e) {
				e.printStackTrace();
			} catch (IllegalAccessException e) {
				e.printStackTrace();
			} catch (InvocationTargetException e) {
				e.printStackTrace();
			}
			
		}
		return personMap;
	}
	
	private void mapIterator(Map map){
		for(Object key:map.keySet()){
			System.out.println(key+":"+map.get(key));
		}
	}
	
	/**
	 * @param personMap
	 * @return
	 * 把Map对象中的值注入到Person对象中
	 * 1.遍历Map，从Map获取属性名及值
	 * 2.通过set设置Person的属性值
	 */
	public Person convertMap2Person(Map personMap){
		Person person=new Person();
		Class clazz=person.getClass();
		for(Object key:personMap.keySet()){
			String fieldName=key.toString();
			try {
				Class type=clazz.getDeclaredField(fieldName).getType();
				Object value=personMap.get(key);
				String methodName="set"+StringUtil.firstCharToUpper(fieldName);
				Method method=clazz.getMethod(methodName,type);
				method.invoke(person, Class.forName(type.getCanonicalName()).getConstructor(String.class).newInstance(value));
			} catch (SecurityException e) {
				e.printStackTrace();
			} catch (NoSuchFieldException e) {
				e.printStackTrace();
			} catch (NoSuchMethodException e) {
				e.printStackTrace();
			} catch (IllegalArgumentException e) {
				e.printStackTrace();
			} catch (IllegalAccessException e) {
				e.printStackTrace();
			} catch (InvocationTargetException e) {
				e.printStackTrace();
			} catch (InstantiationException e) {
				e.printStackTrace();
			} catch (ClassNotFoundException e) {
				e.printStackTrace();
			}
		}
		return person;
	}
}
